public class LearnOOP {
    public static void main(String[] args) {

        // var p1 = new Person("dong", 20, new Info(110, "北京"));

        // System.out.println(p1.toString());
        // System.out.println(p1.getName());

        var s1 = new Student("xi", 30, "class_onde");
        System.out.println(s1);
        System.out.println(s1.getName());

        // 子类向上转型
        Person p2 = new Student("nan", 40, "class_two");
        System.out.println(p2);

        // 通过instanceof操作符 判断是否可转型
        // System.out.println(p1 instanceof Student);
        System.out.println(p2 instanceof Student);
        System.out.println(s1 instanceof Person);

        // 抽象
        Person p3 = new Student("xiao ming", 20, "class_one");
        p3.doing(p3.drinkThing());

        Person p4 = new Teacher("Mr.li", 30);
        p4.doing(p4.eatThing());
    }
}

/**
 * Animal 动物接口
 */
interface Animal {
    // 吃
    String eatThing();

    // 喝
    String drinkThing();
}

/**
 * Info 用户信息
 */
class Info {
    protected int phone;
    protected String address;

    public Info(int phone, String address) {
        this.phone = phone;
        this.address = address;
    }

    public Info() {
    }
}

/**
 * Person 用户类
 */
abstract class Person implements Animal {
    // 定义 继承内部 filed
    protected String name;
    protected int age;
    protected Info info;

    // 重构
    // 可创建Person对象时初始化值
    public Person(String name, int age, Info info) {
        this.name = name;
        this.age = age;
        this.info = info;
    }

    // 重构
    // 可不初始化参数
    // 未声明重载方法，不用手动添加
    public Person() {
    }

    // 重构
    // 添加Override注解，可检测是否正确重写
    @Override
    public String toString() {
        return String.format("%s %d %d %s", name, age, info.phone, info.address);
    }

    public String getName() {
        return String.format("person name : %s", name);
    }

    // final 禁止Override
    public final void setAge(int age) {
        this.age = age;
    }

    public void setName(String name) {
        this.name = name;
    }

    @Override
    public String eatThing() {
        return "吃东西";
    }

    @Override
    public String drinkThing() {
        return "喝水";
    }

    public abstract void doing(String event);
}

/**
 * Student 学生类 继承 用户类 , 实现动物接口
 */
class Student extends Person {
    private String className;

    public String toString() {
        // super 父类对象
        return String.format("%s %d %s", super.name, super.age, className);
    }

    @Override
    public String getName() {
        return String.format("student name : %s", super.name);
    }

    public Student(String name, int age, String className) {
        // super(filed1,filed2) 调用父类构造方法
        super(name, age, new Info());
        this.className = className;
    }

    public Student(String className) {
        this.className = className;
    }

    @Override
    public void setName(String name) {
        super.setName(name);
    }

    @Override
    public void doing(String event) {
        System.out.printf("%s正在%s\n", super.name, event);
    }
}

/**
 * Teacher 老师类, 实现动物接口
 */
class Teacher extends Person {
    public Teacher(String name, int age) {
        // super(filed1,filed2) 调用父类构造方法
        super(name, age, new Info());
    }

    @Override
    public void doing(String event) {
        System.out.printf("%s正在%s\n", this.name, event);
    }
}
